#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/stat.h>
#include <linux/proc_fs.h>
#include <asm-generic/uaccess.h>
#include <linux/list.h>
#include <linux/vmalloc.h>
#include <linux/kthread.h>

/* Nombres de las entradas */
#define PROC_DIR		"aisoclip"
#define CLIPBOARD		"clipboard"
#define SELECTION_CLIP	"selection"
#define PERIOD_CLIP 	"periodo"

/* Valores validos de NCLIP */
#define NCLIP_MIN 1
#define NCLIP_MAX 10

/* Maxima longitud de cadena de caracteres admitida */
#define MAX_LENGTH 1024

/* Funciones externas */
int create_proc_dir_custom (char* directory, struct proc_dir_entry** proc_dir, struct proc_dir_entry** proc_parent);
void remove_proc_dir_custom (char* directory, struct proc_dir_entry** proc_dir, struct proc_dir_entry** proc_parent);
int create_proc_entry_custom (char* entry, struct proc_dir_entry** proc_file, struct proc_dir_entry** proc_parent);
void remove_proc_entry_custom (char* entry, struct proc_dir_entry** proc_file, struct proc_dir_entry** proc_parent);

/* Thread principal */
int kernel_func(void *data);

/* Thread creado al escribir en "PERIOD" */
int kernel_func_wake(void *data);

/* Cambio del clipboard activo */
void change_clip(int i);

/* Funcion de lectura del clipboard activo */
int read_proc_clipboard(char *buffer, char **buffer_location, off_t offset, int buffer_length, int *eof, void *data);

/* Funcion de lectura del clipboard "selection" */
int read_proc_selection(char *buffer, char **buffer_location, off_t offset, int buffer_length, int *eof, void *data);

/* Funcion de lectura del clipboard "periodo" */
int read_proc_period(char *buffer, char **buffer_location, off_t offset, int buffer_length, int *eof, void *data);

/* Funcion de escritura del clipboard activo */
int write_proc_clipboard(struct file *filepointer, const char __user *buffer, unsigned long len, void *data);

/* Funcion de escritura del clipboard "periodo" */
int write_proc_period(struct file *filepointer, const char __user *buffer, unsigned long len, void *data);

/* Funcion de escritura de la entrada "selection" */
int write_proc_selection(struct file *filepointer, const char __user *buffer, unsigned long len, void *data);

/* Funcion invocada al cargar el modulo */
int modulo_carga(void);

/* Funcion invocada al descargar el modulo */
void modulo_descarga(void) ;

